import "github-markdown-css/github-markdown-light.css";
import "antd/dist/reset.css";

import React, { useEffect, useRef, useState } from "react";
import ReactMarkdown from "react-markdown";
import remarkGfm from "remark-gfm";
import { Prism as SyntaxHighlighter } from "react-syntax-highlighter";
import { oneDark } from "react-syntax-highlighter/dist/esm/styles/prism";
import { Button, Input, Avatar, Select, Space } from "antd";
import { UserOutlined } from "@ant-design/icons";

const { Option } = Select;

const App = () => {
  const [messages, setMessages] = useState([]); // 存储多轮对话
  const [inputValue, setInputValue] = useState(""); // 输入框内容
  const [role, setRole] = useState("前端开发"); // 默认角色
  const [isFetching, setIsFetching] = useState(false);
  const contentEndRef = useRef(null);
  const containerRef = useRef(null);
  const [shouldAutoScroll, setShouldAutoScroll] = useState(true);
  const abortControllerRef = useRef(null);

  const roles = [
    { value: "前端开发", label: "前端开发", color: "blue" },
    { value: "后端开发", label: "后端开发", color: "green" },
    { value: "UI设计", label: "UI设计", color: "purple" },
    { value: "测试", label: "测试", color: "orange" },
    { value: "讲师", label: "讲师", color: "red" },
  ];

  const fetchStreamData = async () => {
    if (!inputValue.trim()) return;

    setIsFetching(true);
    const userMessage = { role: "user", content: inputValue, id: Date.now() }; // 添加唯一ID
    setMessages((prev) => [...prev, userMessage]); // 添加用户消息
    setInputValue(""); // 清空输入框

    const controller = new AbortController();
    abortControllerRef.current = controller;

    try {
      const bodyMessages = JSON.stringify({
        messages: [
          { role: "system", content: `你是一名专业的${role}` },
          ...messages,
          userMessage,
        ],
      });
      console.log("bodyMessages:", bodyMessages);
      const response = await fetch("http://localhost:3000/stream-chat", {
        method: "POST",
        headers: { "Content-Type": "application/json" },
        body: bodyMessages,
        signal: controller.signal,
      });

      const reader = response.body.getReader();
      const currentRole = roles.find((r) => r.value === role);
      const assistantMessage = {
        role: "assistant",
        content: "",
        id: Date.now() + 1, // 为回答生成唯一ID
        roleName: currentRole.label,//保存角色名称
        roleColor: currentRole.color,//保存角色颜色
      };
      setMessages((prev) => [...prev, assistantMessage]); // 先添加空回答

      while (true) {
        const { done, value: chunk } = await reader.read();
        if (done) break;

        assistantMessage.content += new TextDecoder().decode(chunk);
        setMessages((prev) =>
          prev.map((msg) =>
            msg.id === assistantMessage.id
              ? { ...msg, content: assistantMessage.content }
              : msg
          )
        ); // 更新当前回答内容
      }
    } catch (error) {
      if (error.name === "AbortError") {
        console.log("用户请求中断");
        setMessages((prev) => [
          ...prev,
          { role: "system", content: "[用户请求中断]", id: Date.now() },
        ]);
      } else {
        console.error("Error fetching stream:", error);
      }
    } finally {
      setIsFetching(false);
      abortControllerRef.current = null;
    }
  };

  const abortFetch = () => {
    if (abortControllerRef.current) {
      abortControllerRef.current.abort();
      setIsFetching(false);
    }
  };

  useEffect(() => {
    return () => {
      if (abortControllerRef.current) {
        abortControllerRef.current.abort();
      }
    };
  }, []);

  useEffect(() => {
    const container = containerRef.current;
    if (!container) return;

    const handleScroll = () => {
      const tolerance = 5;
      const isAtBottom =
        container.scrollHeight - container.scrollTop - container.clientHeight <=
        tolerance;
      setShouldAutoScroll(isAtBottom);
    };

    container.addEventListener("scroll", handleScroll);
    return () => {
      container.removeEventListener("scroll", handleScroll);
    };
  }, []);

  useEffect(() => {
    if (!shouldAutoScroll || !containerRef.current) return;

    const container = containerRef.current;
    requestAnimationFrame(() => {
      container.scrollTop = container.scrollHeight;
    });
  }, [messages, shouldAutoScroll]);

  return (
    <div style={{ height: "100vh", display: "flex", flexDirection: "column" }}>
      <h1>流式数据实时展示</h1>
      <div
        ref={containerRef}
        className="markdown-body"
        style={{
          flex: 1,
          maxHeight: "calc(100vh - 120px)",
          overflowY: "scroll",
          padding: "10px",
          marginBottom: "10px",
        }}
      >
        {messages.map((msg) => (
          <div key={msg.id} style={{ marginBottom: "20px" }}>
            <Space>
              <Avatar
                icon={<UserOutlined />}
                style={{
                  backgroundColor:
                    msg.role === "user"
                      ? "#1890ff"
                      : msg.role === "assistant"
                      ? msg.roleColor //使用消息中保存的颜色
                      : "#f5222d",
                }}
              />
              <span>
                {msg.role === "user"
                  ? "我"
                  : msg.role === "assistant"
                  ? msg.roleName
                  : "系统"}
              </span>
            </Space>
            <ReactMarkdown
              remarkPlugins={[remarkGfm]}
              components={{
                code({ node, inline, className, children, ...props }) {
                  const match = /language-(\w+)/.exec(className || "");
                  return !inline && match ? (
                    <SyntaxHighlighter
                      style={oneDark}
                      language={match[1]}
                      {...props}
                    >
                      {String(children).replace(/\n$/, "")}
                    </SyntaxHighlighter>
                  ) : (
                    <code className={className} {...props}>
                      {children}
                    </code>
                  );
                },
              }}
            >
              {msg.content}
            </ReactMarkdown>
          </div>
        ))}
        <div ref={contentEndRef} />
      </div>
      <div
        style={{
          position: "fixed",
          bottom: 0,
          left: 0,
          right: 0,
          padding: "10px",
          background: "#fff",
          borderTop: "1px solid #e8e8e8",
          zIndex: 1000,
        }}
      >
        <Space style={{ width: "100%", justifyContent: "space-between" }}>
          <Select value={role} onChange={setRole} style={{ width: 120 }}>
            {roles.map((r) => (
              <Option key={r.value} value={r.value}>
                {r.label}
              </Option>
            ))}
          </Select>
          <Input
            value={inputValue}
            onChange={(e) => setInputValue(e.target.value)}
            placeholder="请输入问题"
            onPressEnter={fetchStreamData}
            style={{ flex: 1, margin: "0 10px" }}
            disabled={isFetching}
          />
          <Button
            type="primary"
            onClick={fetchStreamData}
            disabled={isFetching || !inputValue.trim()}
          >
            {isFetching ? "提问中 ..." : "提问"}
          </Button>
          {isFetching && (
            <Button onClick={abortFetch} danger>
              中断
            </Button>
          )}
        </Space>
      </div>
    </div>
  );
};

export default App;
